package com.weareint.common.advices;

import com.alibaba.fastjson.JSONObject;
import com.weareint.common.config.ApplicationProperties;
import com.weareint.common.system.service.IApiInfoService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.ApplicationArguments;
import org.springframework.boot.ApplicationRunner;
import org.springframework.core.env.Environment;
import org.springframework.stereotype.Component;
import springfox.documentation.service.Operation;
import springfox.documentation.spring.web.DocumentationCache;

import java.util.Arrays;
import java.util.List;

/**
 * <pre>
 *     使用应用启动完成之后打印参数
 *     会运行在容器启动完成事件发布之前
 * </pre>
 *
 */
@Slf4j
@Component
public class AfterApplicationStartedListener implements ApplicationRunner {

    @Autowired
    private ApplicationProperties applicationProperties;

    @Autowired
    private Environment environment;

    @Autowired
    private DocumentationCache documentationCache;

    @Autowired
    private IApiInfoService apiInfoService;

    @Override
    public void run(ApplicationArguments args) throws Exception {
        if (applicationProperties.getAuthConfig().isUpdateApis()){
            internalUpdateApis();
        }
        if (log.isInfoEnabled()){
            log.info("[Active Profiles]: " + Arrays.asList(environment.getActiveProfiles()));
            log.info("[Swagger2 Enabled]: " + applicationProperties.getSwagger2().isEnable()
                    + ". http://localhost:" + environment.getProperty("server.port") + "/swagger-ui");
            log.info("[Update Apis to database]: " + applicationProperties.getAuthConfig().isUpdateApis());
        }

    }

    private void internalUpdateApis() {
        // 更新所有URL到数据库
        documentationCache.all().values().forEach(documentation -> {
            documentation.getApiListings().forEach((key, values) -> {
                values.forEach(value -> {
                    value.getApis().forEach(api -> {
                        IApiInfoService dto = new IApiInfoService();
                        dto.setGroupName(api.getGroupName().orElse(null));
                        dto.setPath(api.getPath());
                        dto.setDescription(api.getDescription());
                        List<Operation> operations = api.getOperations();
                        if (!operations.isEmpty()){
                            Operation operation = operations.get(0);
                            dto.setMethod(operation.getMethod().name());
                            dto.setSummary(operation.getSummary());
                            dto.setTags(null == operation.getTags() ? null : StringUtils.join(operation.getTags(), ", "));
                        }
                        if (log.isDebugEnabled()){
                            log.debug(JSONObject.toJSONString(dto));
                        }
                        apiInfoService.saveOrUpdate(dto);
                    });
                });
            });
        });
    }


}
